﻿using System;
using System.Collections.Generic;
using System.Reflection;

namespace Common.Exceptional.Routing
{
    public class ExceptionMessage
    {
        protected ExceptionMessage()
        {
            ShouldContinueRouting = true;
            ProcessedHandlers = new List<Type>();
        }

        public ExceptionMessage(Exception exception)
            : this()
        {
            Exception = exception;
            RawExceptionType = Exception.GetType();
        }

        /// <summary>
        /// 该异常消息携带的异常
        /// </summary>
        public Exception Exception { get; protected set; }

        /// <summary>
        /// 停止路由，表示该异常不需要报告给后续的处理器
        /// </summary>
        public void StopRouting()
        {
            ShouldContinueRouting = false;
        }

        /// <summary>
        /// 表示该异常消息是否需要继续处理
        /// </summary>
        public bool IsHandled { get; set; }

        /// <summary>
        /// 是否已经记录
        /// </summary>
        public bool IsLogged { get; set; }

        /// <summary>
        /// 表示该异常是否需要继续传递给后续的处理器
        /// </summary>
        public bool ShouldContinueRouting { get; protected set; }

        /// <summary>
        /// 异常类型
        /// </summary>
        public Type RawExceptionType { get; set; }

        /// <summary>
        /// 表示该异常已经被哪些处理器处理
        /// </summary>
        public IList<Type> ProcessedHandlers { get; protected set; }

        /// <summary>
        /// 表示该异常由哪个模块抛出
        /// </summary>
        public Assembly ThrownFrom { get; set; }

        /// <summary>
        /// 表示该异常由哪个模块捕捉并发起路由
        /// </summary>
        public Assembly RoutedFrom { get; set; }

        public string Channel { get; set; }

        /// <summary>
        /// 获取异常的明确类型的实例
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <returns></returns>
        public T Unwrap<T>() where T : Exception
        {
            return Exception as T;
        }
    }
}